package 模拟实现队列;

public class MyLinkQueue {
    //创建静态内部类,实例对象作为队列中的节点
    public static class Node{
        int data;//存放数据
        Node next;//存放下一个节点信息
        Node per;//存放前一个节点信息
        //构造方法
        public Node(int data) {
            this.data = data;
        }
    }
    //头结点,指向队列中第一个节点
    private Node front;
    //尾节点,指向队列最后一个节点
    private Node rear;
    //记录队列中节点个数
    private int useSize;
    //为了体现队列的先进先出特点,规定从尾入,从头出(也可以头进尾出)

    //插入操作,原理为双链表的尾插法
    boolean offer(int val){
        Node node = new Node(val);
        if (isEmpty()){
            front = node;
            rear = node;
        }else{
            rear.next = node;
            node.per = rear;
            rear = node;
        }
        useSize++;
        return true;
    }

    //将队头元素出队列
    int poll(){
        if (isEmpty()){
            //队列为空,抛异常,提示不能对空队列进行出队操作
            throw new EmptyException("队列为空,操作错误!!");
        }
        //用ret记录返回的队头元素的数据
        int ret = front.data;
        if (front.next == null){
            front = null;
            rear = null;
            useSize--;
            return ret;
        }
        front = front.next;
        front.per = null;
        useSize--;
        return ret;
    }

    //获取队头元素的值,不出队列
    int peek(){
        if (isEmpty()){
            return -1;
        }
        return front.data;
    }

    //获取队列的长度
    int size(){
        return useSize;
    }

    //判断队列是否为空
    boolean isEmpty(){
        //当队列的头结点为null时,说明队列为空
        return front==null;
    }
}
